package org.bdware.doip.core.codec;

import io.netty.buffer.ByteBuf;
import io.netty.buffer.Unpooled;
import io.netty.channel.ChannelHandler;
import io.netty.channel.ChannelHandlerContext;
import io.netty.handler.codec.MessageToMessageCodec;
import io.netty.handler.ssl.SslHandler;
import org.apache.log4j.Logger;
import org.bdware.doip.core.crypto.GlobalCertifications;
import org.bdware.doip.core.doipMessage.*;
import org.bdware.doip.core.exception.DoDecodeException;

import javax.net.ssl.SSLPeerUnverifiedException;
import javax.net.ssl.SSLSession;
import javax.security.cert.X509Certificate;
import java.util.List;

@ChannelHandler.Sharable
public class DelimiterMessageClientCodec extends MessageToMessageCodec<ByteBuf, DoipMessage> {

    private static Logger logger = Logger.getLogger(DelimiterMessageClientCodec.class);
    DelimiterMessageCodec codec = new DelimiterMessageCodecImpl();

    @Override
    protected void encode(ChannelHandlerContext ctx, DoipMessage msg, List<Object> out){

        try{
            logger.debug("client encode message");
            ByteBuf buff = Unpooled.directBuffer();
            byte[] reqBytes = codec.RequestToBytes(msg);
            buff.writeBytes(reqBytes);
            logger.info("client sending message: "+ new String(reqBytes));
            out.add(buff);
        }catch (Exception e){
            e.printStackTrace();
        }
    }

    @Override
    protected void decode(ChannelHandlerContext ctx, ByteBuf msg, List<Object> out){
        try {
            logger.debug("client decode message");
            SSLSession ss = ctx.pipeline().get(SslHandler.class).engine().getSession();

            if (GlobalCertifications.needAuthentication) {
                X509Certificate cert = null;
                try {
                    cert = ss.getPeerCertificateChain()[0];
                } catch (SSLPeerUnverifiedException e) {
                    e.printStackTrace();
                }
                /*
                String info = null;
                // 获得证书版本
                info = String.valueOf(cert.getVersion());
                System.out.println("证书版本:" + info);
                // 获得证书序列号
                info = cert.getSerialNumber().toString(16);
                System.out.println("证书序列号:" + info);
                // 获得证书有效期
                Date beforedate = cert.getNotBefore();
                info = new SimpleDateFormat("yyyy/MM/dd").format(beforedate);
                System.out.println("证书生效日期:" + info);
                Date afterdate = (Date) cert.getNotAfter();
                info = new SimpleDateFormat("yyyy/MM/dd").format(afterdate);
                System.out.println("证书失效日期:" + info);
                // 获得证书主体信息
                info = cert.getSubjectDN().getName();
                System.out.println("证书拥有者:" + info);
                // 获得证书颁发者信息
                info = cert.getIssuerDN().getName();
                System.out.println("证书颁发者:" + info);
                // 获得证书签名算法名称
                info = cert.getSigAlgName();
                System.out.println("证书签名算法:" + info);

                 */
            }
            byte[] responseBytes = new byte[msg.readableBytes()];
            msg.readBytes(responseBytes);
            DoipMessage inMsg;
            logger.info("client received message: "+ new String(responseBytes));
            inMsg = codec.BytesToResponse(responseBytes);
            out.add(inMsg);
        } catch (DoDecodeException e) {
            e.printStackTrace();
        }
    }

}
